<?php
declare(strict_types=1);

namespace SixShop\Lakala\Service;

use app\model\Order;
use app\model\OrderGoods;
use SixShop\Core\Exception\LogicException;
use SixShop\Lakala\Enum\WechatOrderStateEnum;
use SixShop\Lakala\Model\LakalaWechatPaymentModel;
use SixShop\Payment\Model\ExtensionPaymentModel;
use SixShop\Wechat\Entity\WechatDeliveryEntity;
use SixShop\Wechat\Service\ExpressService;
use think\db\Query;
use think\facade\Log;
use think\Paginator;

class PaymentRecordService
{
    public function __construct(private ExpressService $expressService)
    {
    }

    public function getTradeOrderList(array $params, array $pageAndLimit): Paginator
    {
        $paginator = ExtensionPaymentModel::alias('p')
            ->leftJoin('order o', 'o.id = p.order_id')
            ->leftJoin('lakala_wechat_payment w', 'p.id = w.payment_id')
            ->where([
                'p.pay_type' => 'lakala',
                'p.status' => 2
            ])
            ->when($params['order_sn'], function (Query $query) use ($params) {
                $query->whereLike('o.order_sn', '%' . $params['order_sn'] . '%');
            })
            ->when($params['out_trade_no'], function (Query $query) use ($params) {
                $query->whereLike('p.out_trade_no', '%' . $params['out_trade_no'] . '%');
            })
            ->when($params['transaction_id'], function (Query $query) use ($params) {
                $query->whereLike('p.transaction_id', '%' . $params['transaction_id'] . '%');
            })
            ->when($params['wechat_transaction_id'], function (Query $query) use ($params) {
                $query->whereLike('w.wechat_transaction_id', '%' . $params['wechat_transaction_id'] . '%');
            })
            ->field([
                'p.id',
                'p.order_sn',
                'p.out_trade_no',
                'p.transaction_id',
                'p.amount',
                'p.payment_time',
                'o.express_name',
                'o.express_number',
                'o.shipping_status',
                'o.consignee',
                'o.mobile',
                'o.province',
                'o.city',
                'o.district',
                'o.address',
                'w.id as wechat_payment_id',
                'w.wechat_transaction_id',
                'w.order_state',
                'w.goods_desc',
                'w.express_company',
                'w.express_company_name',
                'w.update_time',
            ])
            ->order('p.id', 'DESC')
            ->paginate($pageAndLimit);
        $paginator->each(function (ExtensionPaymentModel $item) {
            if ($item['order_state'] == null) {
                $wechatOrder = $this->createWechatOrder($item->id);
                $item->setAttrs([
                    'wechat_transaction_id' => $wechatOrder['wechat_transaction_id'],
                    'order_state' => $wechatOrder['order_state'],
                    'goods_desc' => $wechatOrder['goods_desc'],
                    'order_state_text' => $wechatOrder['order_state']->toString(),
                ]);
            } else {
                $item->setAttr('order_state_text', WechatOrderStateEnum::from($item['order_state'])->toString());
            }
        });
        return $paginator;
    }

    public function createWechatOrder(int $paymentID): LakalaWechatPaymentModel
    {
        $payment = ExtensionPaymentModel::find($paymentID);
        $goods = OrderGoods::where(['order_id' => $payment['order_id']])->find();
        return LakalaWechatPaymentModel::create([
            'payment_id' => $payment['id'],
            'wechat_transaction_id' => $payment['payment_result']['acc_trade_no'],
            'order_state' => WechatOrderStateEnum::PENDING_SHIPMENT,
            'goods_desc' => $goods['goods_name'],
        ]);
    }

    /**
     * 更新微信发货状态
     */
    public function updateWechatOrder(int $paymentID): void
    {
        $wechatPayment = LakalaWechatPaymentModel::where(['payment_id' => $paymentID])->find();
        try {
            $result = $this->expressService->queryOrder($wechatPayment->wechat_transaction_id);
        } catch (LogicException $e) {
            return;
        }
        $orderState = WechatOrderStateEnum::from($result['order_state']);
        if ($orderState != $wechatPayment->order_state) {
            $wechatPayment->order_state = $orderState;
            $wechatPayment->save();
        }
        if ($orderState === WechatOrderStateEnum::PENDING_SHIPMENT) {
            $payment = ExtensionPaymentModel::find($paymentID);
            $goods = OrderGoods::where(['order_id' => $payment['order_id']])->find();
            $order = Order::find($payment['order_id']);
            if ($wechatPayment->express_company == null) {
                $delivery = WechatDeliveryEntity::where(['delivery_name' => $order['express_name']])->findOrEmpty();
                if ($delivery->isEmpty()) {
                    // 未找到从历史记录查找
                    $wechatPayment->express_company_name = $order['express_name'];
                    $successPayment = LakalaWechatPaymentModel::where('express_company_name', $order['express_name'])
                        ->whereNotNull('express_company')
                        ->findOrEmpty();
                    if (!$successPayment->isEmpty()) {
                        $wechatPayment->express_company = $successPayment->express_company;
                    }
                    $wechatPayment->save();
                    if ($successPayment->isEmpty()) {
                        Log::warning('未找到物流公司 {transaction_id} {express_company_name}', [
                            'transaction_id' => $wechatPayment->wechat_transaction_id,
                            'express_company_name' => $order['express_name'],
                        ]);
                        return;
                    }
                } else {
                    $wechatPayment->express_company = $delivery['delivery_id'];
                    $wechatPayment->express_company_name = $delivery['delivery_name'];
                    $wechatPayment->save();
                }
            }
            try {
                $this->expressService->uploadShippingInfo(
                    transactionID: $wechatPayment->wechat_transaction_id,
                    openid: $payment['payment_result']['acc_resp_fields']['user_id'],
                    shippingList: [
                        [
                            'tracking_no' => $order['express_number'],
                            'express_company' => $wechatPayment->express_company,
                            'item_desc' => $goods['goods_name'],
                            'contact' => [
                                'receiver_contact' => substr_replace($order['mobile'], '****', -8, 4),
                            ]
                        ],
                    ]
                );
            } catch (LogicException $e) {
                return;
            }
        }
    }
}